SlideShare a Scribd company logo
1 of 70
Mobile Translation System
                        in Crowdsourcing


Stefano Zingarini
Luca Figoli
About Us




    xiaprojects.com  &  @xiateam




2
Our Projects




3
About Us
    Chi	
  siamo
    Dal  1998  sviluppiamo  so/ware  per  ges4one  da4  su  interfaccia  Web  
    Nel  2004  realizzata  prima  versione  piaAaforma  RAD  e  BPM  -­‐
    Dal  2009  introdoAa  estensione  Mobile  Mul4piaAaforma  
    (                ,            ,                  ,  ,                                  )
    Reparto  R&D  con  20  dipenden4  tecnici  (job@apparound.com)

    Il	
  Prodo.o	
  e	
  le	
  Soluzioni
    AAraverso  gli  strumen4  RAD  e  BPM  offer4  dalla  nostra  piaAaforma  
    possiamo  realizzare  velocemente  applicazioni  Mobile  Mul4piaAaforma  in  
    grado  di  ges4re,  da4,  contenu4  e  processi

    Chi	
  ha	
  scelto	
  al	
  nostra	
  tecnologia



4
About Us


    ERP/Web




    Enterprise/SaaS Apps
5
Intro: Roundup	


           Internazionalizzazione del
                  software oggi

         Interazione Software / Utente

          La soluzione Tiyla: Goals &
                   Examples

6
Software & i18n


    Problematica non nuova ma attualissima

                Internazionalizzazione
     “Progettazione per mercati diversi da quello di origine in cui
                            si sviluppa”


                       Localizzazione
    “Le azioni volte a rendere il software fruibile per tali mercati”



7
Why i18n is a chance

    11 persone su 12 nel mondo non conoscono
                     l’Inglese
          Psicologicamente rassicurante
      pagare per un’App da poter usare nella
                  propria lingua

        Affinità culturali trasversali alle lingue

    Raggiungere nuovi mercati / paesi non in crisi

8
Markets For All

       Markets Mobile & Desktop
    Multi-language and Multi Country
              Billing Support




9
With great opportunities...              few problems



                         Sviluppo
       • Supporto nativo i18n diverso per ogni
         dispositivo
       • Gestione “script automatici” traduzioni
         attraverso un sw specifico: integrazione?
       • Distribuzione delle traduzioni in diversi formati
         (crossplatform)



10
With great opportunities...             few problems



                           Gestione
       •   A chi rivolgersi per le traduzioni
       •   Come gestire le collaborazioni
       •   Come gestire la validazione della traduzione
       •   Tenere sotto controllo il processo per più
           lingue e più fornitori




11
With great opportunities...          few problems



                     Pubblicazione

     • Ri-Pubblicazione dell’applicativo quando è
      disponibile una nuova lingua
      • Diversi store / versioni
      • Tempi di attesa
      • Possibilità di reject (per qualsiasi fantasioso
        motivo)

12
Our Solution: Tiyla


       Crossplatform            Crowdsourcing


     Libraries                      Collaboration


                  Api      Process Control


13
Tiyla Components


     Database          AS    Crossplatform
     • Community                 Api Libs
     • Applicazione    API       Gui Libs
     • Crowdsourcing          Admin Manager




14
Tiyla Components Interaction




15
3 core of Tiyla solution


          Trasparenza

           Flessibilità

         Crowdsourcing

16
Tiyla & Trasparenza

        Esigenza di Traduzioni “Trasparenti”
               con Tiyla nel Backend
                          (es Software Enterprise)


     • Supporto alla crew di traduzione aziendale o ai
       Partner in outsourcing tramite Tiyla
     • Offerta traduzioni Tiyla Crew dai nostri partner
     • Disponibilità delle traduzioni di default “Community”
     • Generazione dei file per i18n multipiattaforma da
       includere offline
17
Tiyla & Trasparenza
      Le traduzioni sono generate all’atto della
             compilazione del progetto.


        Plugin Ambiente              Tiyla Desktop
           di sviluppo
     • Il sistema Tiyla è completamente nascosto all’utente
       finale
     • L’azienda rimane proprietaria delle proprie traduzioni
       seguendone workflow & deploy
18
Tiyla & Trasparenza

                            Workflow “Standard”


     • Registrazione  App
     • Abilitazione  Crew




19
Pannello di controllo Developer (OSx)




20
Tiyla & Trasparenza

                            Workflow “Standard”


     • Registrazione  App     • Traduzione
     • Abilitazione  Crew        • Da  Partner
                                 • Da  Community
                                 • Da  Tiyla  Crew




21
Pannello di controllo Traduzione (Win)




22
Tiyla & Trasparenza

                            Workflow “Standard”

                                                     • File  i18n  generato  
                                                       da  Plugin  in  IDE
                                                     • File  i18n  generato  
     • Registrazione  App     • Traduzione             da  Desktop  Client  
     • Abilitazione  Crew        • Da  Partner         da  includere  al  
                                 • Da  Community       progeOo
                                 • Da  Tiyla  Crew




             SELL
                                                     • Build
23
Tiyla & Flessibilità

     Si abilita l’update dell’i18n App Remoto

     • Inclusione di un set base di lingue
     • Update remoto (via Api) di nuove lingue per l’app
       quando queste vengono validate
     • Possibilità di contribuire / usufruire del db
       Community delle traduzioni



24
Tiyla & Flessibilità

              Vantaggi: Tempo = Denaro

     • Possibilità di pubblicare l’applicazione partendo da
       una lingua base (abbattere i tempi di debutto sul
       mercato)
     • Arricchire l’app “on the fly” senza bisogno di
       ripubblicarla
     • Correggere le traduzioni al volo


25
Tiyla & Flessibilità

                            Workflow Tiyla On The FLy
                                   • File  i18n  generato  
                                     da  Plugin  in  IDE
     • Registrazione  App          • File  i18n  generato  
     • Abilitazione  Crew            da  Desktop  Client  
                                     da  includere  al  
                                     progeOo
                                                                     • Build
     • Traduzione
        • Da  Partner
        • Da  Commuinity
        • Da  Tiyla  Crew


                                  • Correzioni
26
                                  • Nuove  Lingue             SELL
Tiyla & Crowdsourcing




        Perchè fa Fico?




27
Tiyla & Crowdsourcing

         Innumerevoli casi di successo...




     ...anche nell’ambito delle traduzioni sw



28
Tiyla & Crowdsourcing




29
Tiyla & Crowdsourcing

     Infrastruttura:
     • Gestione di base Utenti
     • Traduzione degli utenti a partire da una lingua        E
                                                            LU
       certificata                            E            VA
                                           LU
     • Rating delle traduzioni
                                         VA
     • Conteggio attività dell’utente in Crowd Tiyla
       – Rating degli utenti (individuare best & worst)   E
                                                        LU
       – Possibilità di indire contest
                                                      VA
30
Into the Code




          &



31
Tiyla & iOS (1/5)




32
Tiyla & iOS (2/5)




33
Tiyla & iOS (3/5)




34
Tiyla & iOS (4/5)




35
Tiyla & iOS (5/5)




36
iOS + MacOS: Supporto Nativo


     • Prevede un file “Localizzato” aggiunto al bundle del
       progetto
     • Automatico in base alla lingua impostata nel
       dispositivo
     • API da utilizzare
     • Traduce anche i contenuti XIB Disegnati usando il
       Designer


37
iOS + MacOS: Supporto Nativo




38
iOS + MacOS: Supporto Nativo

     Aggiungo la lingua a Localizable.strings




     Completo le traduzioni




39
iOS + MacOS: Supporto Nativo



     NSLocalizedString(@”Hello World”,@”Label Description”);




40
iOS + MacOS: Supporto Nativo


     • Richiede la ricompilazione: File (*) da mettere nel
       bundle
     • Aggiungere un file per ogni nuova lingua da tradurre
     • Modificare tutti i file se cambia la lingua del
       “programmatore”




41
Tiyla & iOS: .h
 //! Profile management
 //! create new profile, or if exist and password match return TRUE
 -(BOOL)registerProfile:(NSString *)email password:(NSString *)password;
 //! verify your password
 -(BOOL)loginProfile:(NSString *)email password:(NSString *)password;
 //! remove profile
 -(BOOL)dropProfile:(NSString *)email password:(NSString *)password;
 //! return data for profile, if password is empty you will receive public informations
 -(NSDictionary *)getProfile:(NSString *)email password:(NSString *)password;
 //! Developer API:
 //! create new Application, if application exists does do nothing
 -(NSString *)registerApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password;
 //! set KeyPairs App info to db
 -(BOOL)setApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password data:(NSDictionary *)data;
 //! Crew manage
 -(BOOL)linkCrew:(NSString *)emailCrew toApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)
 password;
 -(BOOL)unlinkCrew:(NSString *)emailCrew toApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)
 password;
 //! Translations Update Crew
 -(BOOL)setTApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password language:(NSString *)
 language data:(NSDictionary *)data;
 //! Translations Update Developer
 -(BOOL)setTRankApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password language:(NSString *)
 language data:(NSDictionary *)data;
 //! Translations Client
 -(NSDictionary *)getApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password data:(NSDictionary
 *)data;
 //! get Translation * work with shots *
 -(NSDictionary *)getTApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password language:
 (NSString *)language data:(NSDictionary *)data;


42
Tiyla & iOS: RAPI
     +(NSMutableDictionary *)rapi:(NSURL *)url data:(NSDictionary *)data
     {
         //! Data Variables
         NSString *jsonStringEncodedData=nil;
     !   NSData *dataFromJson=nil;
     !   NSData *dataCompressedFromJson=nil;
         NSMutableURLRequest *urlRequest =nil;
         NSData *replyFromServer=nil;
         NSString *replyFromServerString=nil;
         NSMutableDictionary *returnResponse=nil;
         //! JSON Engine
         SBJsonWriter *jsonWriter=[[SBJsonWriter alloc] init];
         SBJsonParser *jsonParser=[[SBJsonParser alloc] init];

         //! Some casts
         jsonStringEncodedData=[jsonWriter stringWithObject:data];
     !   dataFromJson=[jsonStringEncodedData dataUsingEncoding:NSUTF8StringEncoding];
         dataCompressedFromJson=[self gzipData:dataFromJson];
     !
     !   //! Prepare Remote API
     !   urlRequest =[NSMutableURLRequest requestWithURL:url];
     !   [urlRequest setHTTPMethod:@"POST"];
         [urlRequest setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
     !   [urlRequest setHTTPBody:dataCompressedFromJson];
     !   //! Reply RAPI
     !   replyFromServer=[NSURLConnection sendSynchronousRequest:urlRequest returningResponse:nil error:nil];
     !   replyFromServerString=[[NSString alloc] initWithData:replyFromServer encoding:NSASCIIStringEncoding];

         //! JSON Return
         returnResponse=[jsonParser objectWithString:replyFromServerString];
         return returnResponse;!
     }
43
Tiyla & iOS: GZIP

     /**
       * GZip Compression helper for NSData
       */
     +(NSData *)gzipData:(NSData *)pUncompressedData
     {
          z_stream zlibStreamStruct;
          // ...
          int initError = deflateInit2(&zlibStreamStruct, Z_DEFAULT_COMPRESSION, Z_DEFLATED, (15+16), 8,
     Z_DEFAULT_STRATEGY);
          // ...
          NSMutableData *compressedData = [NSMutableData dataWithLength:[pUncompressedData length] * 1.01 + 12];
          // ...
          do
          {
              // ...
              deflateStatus = deflate(&zlibStreamStruct, Z_FINISH);
              // ...! !
          } while ( deflateStatus == Z_OK );
          // ...
          deflateEnd(&zlibStreamStruct);
          // ...
          [compressedData setLength: zlibStreamStruct.total_out];
          // ...
          return compressedData;
     }




44
Tiyla: Server IO GZIP
     <?php
        //  Imposto  il  Xpo  di  ritorno
        header  ("content-­‐type:  applicaXon/json");
        //  Imposto  il  fuso  orario  (il  server  è  in  USA)
        date_default_Xmezone_set('UTC');
        //  DEBUG:  Memorizzo  l'ora  di  partenza  per  calcolare  il  "peso"  in  fondo
        $start_Xme=microXme(TRUE);
        //  ATTENZIONE:  lo  stream  in  ingresso  POST  deve  essere  compresso
        $fp=gzopen("php://input","r");
        //  POST:  leggo  in  input  tuOo  il  JSON  inviato  dai  client
        $data  =  gzread($fp,1024000);  //  1MB  in  upload  (decompresso...)
        //  chiudo  il  descriOore
        fclose($fp);
        $fp=0;
        //  genero  un  array  associaXvo  dal  POST
        $data=json_decode($data,true);
     ?>
45
Tiyla & iOS: Libreria (1/5)




46
Tiyla & iOS: Libreria (2/5)




47
Tiyla & iOS: Libreria (3/5)




48
Tiyla & iOS: Libreria (4/5)




49
Tiyla & iOS: Libreria (5/5)




50
Tiyla & MacOS: Desktop Client




51
Tiyla & MacOS: Desktop Client




52
Into the Code




          &



53
Android: Supporto Nativo

     • Sistema di localizzazione integrato basato su file xml,
       presenti in diverse folder con suffisso differente a seconda
       della lingua (values, values-it, values-fr)
     • Il file chiamato strings.xml è semplicemente un elenco di
       righe chiave – valore dove il valore è appunto la stringa
       tradotta.
     • Da codice per recuperare la stringa corrente getString
       (R.string.key)
     • Se si vuole modificare o aggiungere una nuova lingua
       bisogna ricompilare il programma producendo il nuovo apk
       e pubblicare l’aggiornamento sul market

54
Tiyla & Android: Presentazione




55
Tiyla & Android: API
     //!  Profile  management
     //!  create  new  profile,  or  if  exist  and  password  match  return  TRUE
     sta7c	
  public	
  boolean	
  registerProfile(String	
  email,	
  String	
  password)
     //!  verify  your  password
     sta7c	
  public	
  boolean	
  loginProfile(String	
  email,	
  String	
  password)
     //!  remove  profile
     sta7c	
  public	
  boolean	
  dropProfile(String	
  email,	
  String	
  password)
     //!  return  data  for  profile,  if  password  is  empty  you  will  receive  public  informaXons
     sta7c	
  public	
  JSONObject	
  getProfile(String	
  email,	
  String	
  password)
     //!  Developer  API:
     //!  create  new  ApplicaXon,  if  applicaXon  exists  does  do  nothing
     sta7c	
  public	
  String	
  registerApp(String	
  bundleId,	
  String	
  email,	
  String	
  password)
     //!  set  KeyPairs  App  info  to  db
     sta7c	
  public	
  boolean	
  setApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  JSONObject	
  data)
     //!  Crew  manage
     sta7c	
  public	
  boolean	
  linkCrew(String	
  emailCrew,	
  String	
  bundleId,	
  String	
  email,	
  String	
  password)
     sta7c	
  public	
  boolean	
  unlinkCrew(String	
  emailCrew,	
  String	
  bundleId,	
  String	
  email,	
  String	
  password)
     //!  TranslaXons  Update  Crew
     sta7c	
  public	
  boolean	
  setTApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  String	
  language,	
  JSONObject	
  data)
     //!  TranslaXons  Update  Developer
     sta7c	
  public	
  boolean	
  setTRankApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  String	
  language,	
  JSONObject	
  data)
     //!  TranslaXons  Client
     sta7c	
  public	
  JSONObject	
  getApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  JSONObject	
  data)
     //!  get  TranslaXon  *  work  with  shots  *
     sta7c	
  public	
  JSONObject	
  getTApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  String	
  language,	
  JSONObject	
  data);


56
Tiyla & Android: RAPI

     //Inizialmente  comprimo  i  daX  in  formato  gzip  uXlizzando     //Ricevo  i  daX  dal  server
     //l'oggeOo  GZIPOutputStream                                        InputStream  input  =  connecXon.getInputStream();
     byte[]	
  compressedData	
  =	
  Library.compressData               String  contentEncoding  =  connecXon.getContentEncoding
     (dataS.getBytes());                                                 ();  
                                                                         BufferedInputStream  inputB  =  new	
  BufferedInputStream
     //-­‐-­‐-­‐
                                                                         (input,	
  10000);
     //Apro  una  HOpURLConnecXon  verso  il  server
     connecXon  =  (HOpURLConnecXon)  new	
  URL                         //-­‐-­‐-­‐
     (url).openConnec8on();                                              while	
  ((nRead	
  =	
  inputB.read(data,	
  0,	
  data.length))	
  !=	
  -­‐1)	
  
     //-­‐-­‐                                                            {
     //Imposto  il  parametro  "Accept-­‐Encoding"  "deflate"  per        byteAOSB.write(data,  0,  nRead);
     ricevere  i  daX  in  formato  compresso                            }
     connecXon.addRequestProperty("Accept-­‐Encoding",  "deflate");
     connecXon.setRequestProperty("Content-­‐Type","applicaXon/          //-­‐-­‐        
     json");                                                             //ScompaOo  i  daX  dal  server
                                                                         received_result  =  new	
  String(Library.decompressData
     //Invio  i  daX
                                                                         (received_result.getBytes()));
     connecXon.getOutputStream().write(compressedData);                  //-­‐-­‐        




57
Tiyla & BlackBerry




               • Java
               • Eclipse Sdk




58
Tiyla & Nokia




     QT


59
Into the Code




          &



60
Windows & WP7:
                      Supporto Nativo
     • Sistema di localizzazione integrato basato su file di risorse (resx),
       con nomi organizzati gerarchicamente a partire dal file della lingua
       di default. Ad esempio myRes.resx contiene le informazioni in lingua
       di default, mentre una eventuale traduzione in francese standard si
       ottiene aggiungendo il file myRes.fr.resx al progetto
     • Un file di risorse è composto da una serie di coppie chiave-valore.
       Tutti i file dovrebbero avere le stesse chiavi a cui corrispondono le
       versioni in lingua degli stessi testi
     • Le interfacce utente invocano le stringhe contenute nei file di risorse
       tramite la loro chiave, usando l’operatore binding
     • Se si vuole modificare o aggiungere una nuova lingua bisogna
       ricompilare il programma producendo il nuovo xap e pubblicare
       l’aggiornamento sul market
61
Tiyla & WP7: Presentazione




62
Windows & WP7: Supporto
                Nativo


     • Le chiamate al server in WP7 sono gestite in
       modo asincrono.
     • La libreria mette a disposizione una serie di
       eventi che vengono generati quando la chiamata
       è stata completata.



63
Tiyla & WP7: Metodi (1/3)
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  delegate	
  void	
  OperationCompletedDelegate	
  (String	
  result,	
  Exception	
  error);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  event	
  OperationCompletedDelegate	
  OperationCompleted;
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  Profile	
  management
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  create	
  new	
  profile,	
  or	
  if	
  exist	
  and	
  password	
  match	
  return	
  TRUE
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  registerProfile(String	
  email,	
  String	
  password);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  registerProfile_Completed;


     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  verify	
  your	
  password
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  loginProfile(String	
  email,	
  String	
  password);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  loginProfile_Completed;


     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  remove	
  profile
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  dropProfile(String	
  email,	
  String	
  password);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  dropProfile_Completed;


     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  return	
  data	
  for	
  profile,	
  if	
  password	
  is	
  empty	
  you	
  will	
  receive	
  	
  informations
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  getProfileString(String	
  email,	
  String	
  password);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  getProfileString_Completed;


     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  create	
  new	
  Application,	
  if	
  application	
  exists	
  does	
  do	
  nothing
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  registerApp(String	
  bundleId,	
  String	
  email,	
  String	
  password);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  registerApp_Completed;
64
     	
  	
  	
  	
  	
  	
  	
  	
  
Tiyla & WP7: Metodi (2/3)
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  set	
  KeyPairs	
  App	
  info	
  to	
  db
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  setApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  Dictionary<string,	
  string>	
  data);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  setApp_Completed;

     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  Crew	
  manage
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  linkCrew(String	
  emailCrew,	
  String	
  bundleId,	
  String	
  email,	
  String	
  password);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  linkCrew_Completed;
     	
  	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  Crew	
  manage
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>	
  	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  unlinkCrew(String	
  emailCrew,	
  String	
  bundleId,	
  String	
  email,	
  String	
  password);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  unlinkCrew_Completed;


     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  Translations	
  Update	
  Crew
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  setTApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  String	
  language,	
  Dictionary<string,	
  string>	
  data);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  setTApp_Completed;

     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  Translations	
  Update	
  Developer
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  bool	
  setTRankApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  String	
  language,	
  Dictionary<string,	
  string>	
  data);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  setTRankApp_Completed;

     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  Translations	
  Client
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  getApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  Dictionary<string,	
  string>	
  data);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  getApp_Completed;
65
Tiyla & WP7: Metodi (3/3)



                ///	
  <summary>
                ///	
  get	
  Translation	
  *	
  work	
  with	
  shots	
  *
                ///	
  </summary>	
  	
  	
  	
  	
  	
  	
  
                public	
  void	
  getTApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  String	
  language,	
  Dictionary<string,	
  string>	
  data);
                public	
  OperationCompletedDelegate	
  getTApp_Completed;

     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  <summary>
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  get	
  Translation	
  *	
  work	
  with	
  shots	
  *
     	
  	
  	
  	
  	
  	
  	
  	
  ///	
  </summary>	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  getTApp(String	
  bundleId,	
  String	
  email,	
  String	
  password,	
  String	
  language,	
  Dictionary<string,	
  string>	
  data);
     	
  	
  	
  	
  	
  	
  	
  	
  public	
  OperationCompletedDelegate	
  getTApp_Completed;




66
Tiyla & WP7: RAPI (1/3)

     • Per implementare alcune funzionalità sono
       state usate librerie open source pubblicate da
       CODEPLEX:

     • JSON.NET -
       http://json.codeplex.com/releases/view/64935

     • Silverlight SharpZipLib -
       http://slsharpziplib.codeplex.com/releases/view/50561


67
Tiyla & WP7: RAPI (2/3)
     	
  	
  	
  	
  	
  	
  	
  	
  private	
  void	
  registerProfile(String	
  email,	
  String	
  password,	
  string	
  method	
  =	
  "GET")
     	
  	
  	
  	
  	
  	
  	
  	
  {	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  var	
  sender	
  =	
  new	
  TyilaUtils();
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  sender.MyDownLoadCompletedEvent	
  +=	
  onDownloadCompleted;
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  switch	
  (method)
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  {
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  case	
  "POST":
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  string	
  postData	
  =	
  JsonConvert.SerializeObject(new	
  command3pars()	
  {	
  func	
  =	
  "registerProfile",	
  email	
  =	
  email,	
  
     	
                                                	
                                     	
                 password	
  =	
  password	
  });
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  sender.executeCommandWithPost("http://tiyla.xiaprojects.com/core/echo.php",	
  postData);
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  break;
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  case	
  "GET":
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  default:
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  var	
  theUrlAndGetData	
  =	
  String.Format("func={0}&email={1}&password={2}",	
  "registerProfile",	
  
     	
                                                	
                                     	
                 	
                 HttpUtility.UrlEncode(email),	
  HttpUtility.UrlEncode(password));
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  theUrlAndGetData	
  =	
  "http://tiyla.xiaprojects.com/core/echo.php?"	
  +	
  theUrlAndGetData;
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  sender.executeCommandWithGet(theUrlAndGetData);
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  break;
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  }
     	
  	
  	
  	
  	
  	
  	
  	
  }
     	
  	
  	
  	
  	
  	
  
     	
  	
  	
  	
  	
  	
  	
  	
  private	
  void	
  onDownloadCompleted(TyilaUtils	
  sender,	
  String	
  content,	
  Exception	
  ex)
     	
  	
  	
  	
  	
  	
  	
  	
  {
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  sender.MyDownLoadCompletedEvent	
  -­‐=	
  onDownloadCompleted;
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  if	
  (ex	
  !=	
  null)
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  {
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  MessageBox.Show(ex.Message);
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  }
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  else
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  {
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  MessageBox.Show(content);
     	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  }
     	
  	
  	
  	
  	
  	
  	
  	
  }


68
Tiyla & WP7: RAPI (3/3)

	
  	
  	
  	
  	
  	
  	
  	
  public	
  void	
  executeCommandWithGet(String	
  theUrl)
	
  	
  	
  	
  	
  	
  	
  	
  {
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  var	
  client	
  =	
  new	
  WebClient();
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  client.DownloadStringCompleted	
  +=	
  new	
  	
  	
  	
  	
   	
   	
   	
  	
  	
  
	
                             	
                      DownloadStringCompletedEventHandler(client_DownloadStringCompleted);
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  client.DownloadStringAsync(new	
  Uri(theUrl));
	
  	
  	
  	
  	
  	
  	
  	
  }

	
  	
  	
  	
  	
  	
  	
  	
  private	
  void	
  client_DownloadStringCompleted(object	
  sender,	
  	
  	
  	
  
	
                             DownloadStringCompletedEventArgs	
  e)
	
  	
  	
  	
  	
  	
  	
  	
  {
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  if	
  (MyDownLoadCompletedEvent	
  !=	
  null)
	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  	
  MyDownLoadCompletedEvent(this,	
  e.Result,	
  e.Error);
	
  	
  	
  	
  	
  	
  	
  	
  }




 69
Contact us



     xiaprojects.com  &  @xiateam




      Xyla.com  &  @Xylatweets
70

More Related Content

Similar to Tiyla @Whymca '11

Similar to Tiyla @Whymca '11 (20)

Foss ieri e oggi
Foss ieri e oggiFoss ieri e oggi
Foss ieri e oggi
 
Drupal Day 2011 - Drupal per la ricerca, il caso EAI
Drupal Day 2011 - Drupal per la ricerca, il caso EAIDrupal Day 2011 - Drupal per la ricerca, il caso EAI
Drupal Day 2011 - Drupal per la ricerca, il caso EAI
 
Linux & Tools: per la piccola azienda e i freelance
Linux & Tools: per la piccola azienda e i freelanceLinux & Tools: per la piccola azienda e i freelance
Linux & Tools: per la piccola azienda e i freelance
 
Dalla virtualizzazione al private cloud: Il Patronato INCA rinnova la fiducia...
Dalla virtualizzazione al private cloud: Il Patronato INCA rinnova la fiducia...Dalla virtualizzazione al private cloud: Il Patronato INCA rinnova la fiducia...
Dalla virtualizzazione al private cloud: Il Patronato INCA rinnova la fiducia...
 
Alfresco Day Milano 2016 - TAI
Alfresco Day Milano 2016 - TAIAlfresco Day Milano 2016 - TAI
Alfresco Day Milano 2016 - TAI
 
Implementazione di una soluzione a microservizi: benifici organizzativi ed ec...
Implementazione di una soluzione a microservizi: benifici organizzativi ed ec...Implementazione di una soluzione a microservizi: benifici organizzativi ed ec...
Implementazione di una soluzione a microservizi: benifici organizzativi ed ec...
 
Software libero e open source a costo zero per la grafica
Software libero e open source a costo zero per la graficaSoftware libero e open source a costo zero per la grafica
Software libero e open source a costo zero per la grafica
 
Debugging with-z-ray
Debugging with-z-rayDebugging with-z-ray
Debugging with-z-ray
 
Festivalmente: Getting Things done
Festivalmente: Getting Things doneFestivalmente: Getting Things done
Festivalmente: Getting Things done
 
Sbs 2011 e soluzioni professionali su yashi ypad w7
Sbs 2011 e soluzioni professionali su yashi ypad w7Sbs 2011 e soluzioni professionali su yashi ypad w7
Sbs 2011 e soluzioni professionali su yashi ypad w7
 
ALM Revolutions - What's new in visual studio ALM 11
ALM Revolutions - What's new in visual studio ALM 11ALM Revolutions - What's new in visual studio ALM 11
ALM Revolutions - What's new in visual studio ALM 11
 
2014 - Adobe Digital Publishing Suite (DPS)
2014 -  Adobe Digital Publishing Suite (DPS) 2014 -  Adobe Digital Publishing Suite (DPS)
2014 - Adobe Digital Publishing Suite (DPS)
 
Creare un Information Radiator con Delphi
Creare un Information Radiator con DelphiCreare un Information Radiator con Delphi
Creare un Information Radiator con Delphi
 
Xamarin: Shared Library and Portable Class Library - Aristide Di Francesco - ...
Xamarin: Shared Library and Portable Class Library - Aristide Di Francesco - ...Xamarin: Shared Library and Portable Class Library - Aristide Di Francesco - ...
Xamarin: Shared Library and Portable Class Library - Aristide Di Francesco - ...
 
PMS Modernizzazione_5250
PMS Modernizzazione_5250PMS Modernizzazione_5250
PMS Modernizzazione_5250
 
Costruire applicazioni-cross-platform-con-xamarin-visual-studio-2013
Costruire applicazioni-cross-platform-con-xamarin-visual-studio-2013Costruire applicazioni-cross-platform-con-xamarin-visual-studio-2013
Costruire applicazioni-cross-platform-con-xamarin-visual-studio-2013
 
Alfresco Day Roma 2015: TAI
Alfresco Day Roma 2015: TAIAlfresco Day Roma 2015: TAI
Alfresco Day Roma 2015: TAI
 
Software modularity, microservices ed headless platform all in one. Liferay: ...
Software modularity, microservices ed headless platform all in one. Liferay: ...Software modularity, microservices ed headless platform all in one. Liferay: ...
Software modularity, microservices ed headless platform all in one. Liferay: ...
 
Linuxday2007
Linuxday2007Linuxday2007
Linuxday2007
 
Anatomia di un progetto open-source
Anatomia di un progetto open-sourceAnatomia di un progetto open-source
Anatomia di un progetto open-source
 

Tiyla @Whymca '11

  • 1. Mobile Translation System in Crowdsourcing Stefano Zingarini Luca Figoli
  • 2. About Us xiaprojects.com  &  @xiateam 2
  • 4. About Us Chi  siamo Dal  1998  sviluppiamo  so/ware  per  ges4one  da4  su  interfaccia  Web   Nel  2004  realizzata  prima  versione  piaAaforma  RAD  e  BPM  -­‐ Dal  2009  introdoAa  estensione  Mobile  Mul4piaAaforma   (                ,            ,                  ,  ,                                  ) Reparto  R&D  con  20  dipenden4  tecnici  (job@apparound.com) Il  Prodo.o  e  le  Soluzioni AAraverso  gli  strumen4  RAD  e  BPM  offer4  dalla  nostra  piaAaforma   possiamo  realizzare  velocemente  applicazioni  Mobile  Mul4piaAaforma  in   grado  di  ges4re,  da4,  contenu4  e  processi Chi  ha  scelto  al  nostra  tecnologia 4
  • 5. About Us ERP/Web Enterprise/SaaS Apps 5
  • 6. Intro: Roundup Internazionalizzazione del software oggi Interazione Software / Utente La soluzione Tiyla: Goals & Examples 6
  • 7. Software & i18n Problematica non nuova ma attualissima Internazionalizzazione “Progettazione per mercati diversi da quello di origine in cui si sviluppa” Localizzazione “Le azioni volte a rendere il software fruibile per tali mercati” 7
  • 8. Why i18n is a chance 11 persone su 12 nel mondo non conoscono l’Inglese Psicologicamente rassicurante pagare per un’App da poter usare nella propria lingua Affinità culturali trasversali alle lingue Raggiungere nuovi mercati / paesi non in crisi 8
  • 9. Markets For All Markets Mobile & Desktop Multi-language and Multi Country Billing Support 9
  • 10. With great opportunities... few problems Sviluppo • Supporto nativo i18n diverso per ogni dispositivo • Gestione “script automatici” traduzioni attraverso un sw specifico: integrazione? • Distribuzione delle traduzioni in diversi formati (crossplatform) 10
  • 11. With great opportunities... few problems Gestione • A chi rivolgersi per le traduzioni • Come gestire le collaborazioni • Come gestire la validazione della traduzione • Tenere sotto controllo il processo per più lingue e più fornitori 11
  • 12. With great opportunities... few problems Pubblicazione • Ri-Pubblicazione dell’applicativo quando è disponibile una nuova lingua • Diversi store / versioni • Tempi di attesa • Possibilità di reject (per qualsiasi fantasioso motivo) 12
  • 13. Our Solution: Tiyla Crossplatform Crowdsourcing Libraries Collaboration Api Process Control 13
  • 14. Tiyla Components Database AS Crossplatform • Community Api Libs • Applicazione API Gui Libs • Crowdsourcing Admin Manager 14
  • 16. 3 core of Tiyla solution Trasparenza Flessibilità Crowdsourcing 16
  • 17. Tiyla & Trasparenza Esigenza di Traduzioni “Trasparenti” con Tiyla nel Backend (es Software Enterprise) • Supporto alla crew di traduzione aziendale o ai Partner in outsourcing tramite Tiyla • Offerta traduzioni Tiyla Crew dai nostri partner • Disponibilità delle traduzioni di default “Community” • Generazione dei file per i18n multipiattaforma da includere offline 17
  • 18. Tiyla & Trasparenza Le traduzioni sono generate all’atto della compilazione del progetto. Plugin Ambiente Tiyla Desktop di sviluppo • Il sistema Tiyla è completamente nascosto all’utente finale • L’azienda rimane proprietaria delle proprie traduzioni seguendone workflow & deploy 18
  • 19. Tiyla & Trasparenza Workflow “Standard” • Registrazione  App • Abilitazione  Crew 19
  • 20. Pannello di controllo Developer (OSx) 20
  • 21. Tiyla & Trasparenza Workflow “Standard” • Registrazione  App • Traduzione • Abilitazione  Crew • Da  Partner • Da  Community • Da  Tiyla  Crew 21
  • 22. Pannello di controllo Traduzione (Win) 22
  • 23. Tiyla & Trasparenza Workflow “Standard” • File  i18n  generato   da  Plugin  in  IDE • File  i18n  generato   • Registrazione  App • Traduzione da  Desktop  Client   • Abilitazione  Crew • Da  Partner da  includere  al   • Da  Community progeOo • Da  Tiyla  Crew SELL • Build 23
  • 24. Tiyla & Flessibilità Si abilita l’update dell’i18n App Remoto • Inclusione di un set base di lingue • Update remoto (via Api) di nuove lingue per l’app quando queste vengono validate • Possibilità di contribuire / usufruire del db Community delle traduzioni 24
  • 25. Tiyla & Flessibilità Vantaggi: Tempo = Denaro • Possibilità di pubblicare l’applicazione partendo da una lingua base (abbattere i tempi di debutto sul mercato) • Arricchire l’app “on the fly” senza bisogno di ripubblicarla • Correggere le traduzioni al volo 25
  • 26. Tiyla & Flessibilità Workflow Tiyla On The FLy • File  i18n  generato   da  Plugin  in  IDE • Registrazione  App • File  i18n  generato   • Abilitazione  Crew da  Desktop  Client   da  includere  al   progeOo • Build • Traduzione • Da  Partner • Da  Commuinity • Da  Tiyla  Crew • Correzioni 26 • Nuove  Lingue SELL
  • 27. Tiyla & Crowdsourcing Perchè fa Fico? 27
  • 28. Tiyla & Crowdsourcing Innumerevoli casi di successo... ...anche nell’ambito delle traduzioni sw 28
  • 30. Tiyla & Crowdsourcing Infrastruttura: • Gestione di base Utenti • Traduzione degli utenti a partire da una lingua E LU certificata E VA LU • Rating delle traduzioni VA • Conteggio attività dell’utente in Crowd Tiyla – Rating degli utenti (individuare best & worst) E LU – Possibilità di indire contest VA 30
  • 32. Tiyla & iOS (1/5) 32
  • 33. Tiyla & iOS (2/5) 33
  • 34. Tiyla & iOS (3/5) 34
  • 35. Tiyla & iOS (4/5) 35
  • 36. Tiyla & iOS (5/5) 36
  • 37. iOS + MacOS: Supporto Nativo • Prevede un file “Localizzato” aggiunto al bundle del progetto • Automatico in base alla lingua impostata nel dispositivo • API da utilizzare • Traduce anche i contenuti XIB Disegnati usando il Designer 37
  • 38. iOS + MacOS: Supporto Nativo 38
  • 39. iOS + MacOS: Supporto Nativo Aggiungo la lingua a Localizable.strings Completo le traduzioni 39
  • 40. iOS + MacOS: Supporto Nativo NSLocalizedString(@”Hello World”,@”Label Description”); 40
  • 41. iOS + MacOS: Supporto Nativo • Richiede la ricompilazione: File (*) da mettere nel bundle • Aggiungere un file per ogni nuova lingua da tradurre • Modificare tutti i file se cambia la lingua del “programmatore” 41
  • 42. Tiyla & iOS: .h //! Profile management //! create new profile, or if exist and password match return TRUE -(BOOL)registerProfile:(NSString *)email password:(NSString *)password; //! verify your password -(BOOL)loginProfile:(NSString *)email password:(NSString *)password; //! remove profile -(BOOL)dropProfile:(NSString *)email password:(NSString *)password; //! return data for profile, if password is empty you will receive public informations -(NSDictionary *)getProfile:(NSString *)email password:(NSString *)password; //! Developer API: //! create new Application, if application exists does do nothing -(NSString *)registerApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password; //! set KeyPairs App info to db -(BOOL)setApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password data:(NSDictionary *)data; //! Crew manage -(BOOL)linkCrew:(NSString *)emailCrew toApp:(NSString *)bundleId email:(NSString *)email password:(NSString *) password; -(BOOL)unlinkCrew:(NSString *)emailCrew toApp:(NSString *)bundleId email:(NSString *)email password:(NSString *) password; //! Translations Update Crew -(BOOL)setTApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password language:(NSString *) language data:(NSDictionary *)data; //! Translations Update Developer -(BOOL)setTRankApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password language:(NSString *) language data:(NSDictionary *)data; //! Translations Client -(NSDictionary *)getApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password data:(NSDictionary *)data; //! get Translation * work with shots * -(NSDictionary *)getTApp:(NSString *)bundleId email:(NSString *)email password:(NSString *)password language: (NSString *)language data:(NSDictionary *)data; 42
  • 43. Tiyla & iOS: RAPI +(NSMutableDictionary *)rapi:(NSURL *)url data:(NSDictionary *)data { //! Data Variables NSString *jsonStringEncodedData=nil; ! NSData *dataFromJson=nil; ! NSData *dataCompressedFromJson=nil; NSMutableURLRequest *urlRequest =nil; NSData *replyFromServer=nil; NSString *replyFromServerString=nil; NSMutableDictionary *returnResponse=nil; //! JSON Engine SBJsonWriter *jsonWriter=[[SBJsonWriter alloc] init]; SBJsonParser *jsonParser=[[SBJsonParser alloc] init]; //! Some casts jsonStringEncodedData=[jsonWriter stringWithObject:data]; ! dataFromJson=[jsonStringEncodedData dataUsingEncoding:NSUTF8StringEncoding]; dataCompressedFromJson=[self gzipData:dataFromJson]; ! ! //! Prepare Remote API ! urlRequest =[NSMutableURLRequest requestWithURL:url]; ! [urlRequest setHTTPMethod:@"POST"]; [urlRequest setValue:@"application/json" forHTTPHeaderField:@"Content-Type"]; ! [urlRequest setHTTPBody:dataCompressedFromJson]; ! //! Reply RAPI ! replyFromServer=[NSURLConnection sendSynchronousRequest:urlRequest returningResponse:nil error:nil]; ! replyFromServerString=[[NSString alloc] initWithData:replyFromServer encoding:NSASCIIStringEncoding]; //! JSON Return returnResponse=[jsonParser objectWithString:replyFromServerString]; return returnResponse;! } 43
  • 44. Tiyla & iOS: GZIP /** * GZip Compression helper for NSData */ +(NSData *)gzipData:(NSData *)pUncompressedData { z_stream zlibStreamStruct; // ... int initError = deflateInit2(&zlibStreamStruct, Z_DEFAULT_COMPRESSION, Z_DEFLATED, (15+16), 8, Z_DEFAULT_STRATEGY); // ... NSMutableData *compressedData = [NSMutableData dataWithLength:[pUncompressedData length] * 1.01 + 12]; // ... do { // ... deflateStatus = deflate(&zlibStreamStruct, Z_FINISH); // ...! ! } while ( deflateStatus == Z_OK ); // ... deflateEnd(&zlibStreamStruct); // ... [compressedData setLength: zlibStreamStruct.total_out]; // ... return compressedData; } 44
  • 45. Tiyla: Server IO GZIP <?php //  Imposto  il  Xpo  di  ritorno header  ("content-­‐type:  applicaXon/json"); //  Imposto  il  fuso  orario  (il  server  è  in  USA) date_default_Xmezone_set('UTC'); //  DEBUG:  Memorizzo  l'ora  di  partenza  per  calcolare  il  "peso"  in  fondo $start_Xme=microXme(TRUE); //  ATTENZIONE:  lo  stream  in  ingresso  POST  deve  essere  compresso $fp=gzopen("php://input","r"); //  POST:  leggo  in  input  tuOo  il  JSON  inviato  dai  client $data  =  gzread($fp,1024000);  //  1MB  in  upload  (decompresso...) //  chiudo  il  descriOore fclose($fp); $fp=0; //  genero  un  array  associaXvo  dal  POST $data=json_decode($data,true); ?> 45
  • 46. Tiyla & iOS: Libreria (1/5) 46
  • 47. Tiyla & iOS: Libreria (2/5) 47
  • 48. Tiyla & iOS: Libreria (3/5) 48
  • 49. Tiyla & iOS: Libreria (4/5) 49
  • 50. Tiyla & iOS: Libreria (5/5) 50
  • 51. Tiyla & MacOS: Desktop Client 51
  • 52. Tiyla & MacOS: Desktop Client 52
  • 54. Android: Supporto Nativo • Sistema di localizzazione integrato basato su file xml, presenti in diverse folder con suffisso differente a seconda della lingua (values, values-it, values-fr) • Il file chiamato strings.xml è semplicemente un elenco di righe chiave – valore dove il valore è appunto la stringa tradotta. • Da codice per recuperare la stringa corrente getString (R.string.key) • Se si vuole modificare o aggiungere una nuova lingua bisogna ricompilare il programma producendo il nuovo apk e pubblicare l’aggiornamento sul market 54
  • 55. Tiyla & Android: Presentazione 55
  • 56. Tiyla & Android: API //!  Profile  management //!  create  new  profile,  or  if  exist  and  password  match  return  TRUE sta7c  public  boolean  registerProfile(String  email,  String  password) //!  verify  your  password sta7c  public  boolean  loginProfile(String  email,  String  password) //!  remove  profile sta7c  public  boolean  dropProfile(String  email,  String  password) //!  return  data  for  profile,  if  password  is  empty  you  will  receive  public  informaXons sta7c  public  JSONObject  getProfile(String  email,  String  password) //!  Developer  API: //!  create  new  ApplicaXon,  if  applicaXon  exists  does  do  nothing sta7c  public  String  registerApp(String  bundleId,  String  email,  String  password) //!  set  KeyPairs  App  info  to  db sta7c  public  boolean  setApp(String  bundleId,  String  email,  String  password,  JSONObject  data) //!  Crew  manage sta7c  public  boolean  linkCrew(String  emailCrew,  String  bundleId,  String  email,  String  password) sta7c  public  boolean  unlinkCrew(String  emailCrew,  String  bundleId,  String  email,  String  password) //!  TranslaXons  Update  Crew sta7c  public  boolean  setTApp(String  bundleId,  String  email,  String  password,  String  language,  JSONObject  data) //!  TranslaXons  Update  Developer sta7c  public  boolean  setTRankApp(String  bundleId,  String  email,  String  password,  String  language,  JSONObject  data) //!  TranslaXons  Client sta7c  public  JSONObject  getApp(String  bundleId,  String  email,  String  password,  JSONObject  data) //!  get  TranslaXon  *  work  with  shots  * sta7c  public  JSONObject  getTApp(String  bundleId,  String  email,  String  password,  String  language,  JSONObject  data); 56
  • 57. Tiyla & Android: RAPI //Inizialmente  comprimo  i  daX  in  formato  gzip  uXlizzando   //Ricevo  i  daX  dal  server //l'oggeOo  GZIPOutputStream InputStream  input  =  connecXon.getInputStream(); byte[]  compressedData  =  Library.compressData String  contentEncoding  =  connecXon.getContentEncoding (dataS.getBytes()); ();   BufferedInputStream  inputB  =  new  BufferedInputStream //-­‐-­‐-­‐ (input,  10000); //Apro  una  HOpURLConnecXon  verso  il  server connecXon  =  (HOpURLConnecXon)  new  URL //-­‐-­‐-­‐ (url).openConnec8on(); while  ((nRead  =  inputB.read(data,  0,  data.length))  !=  -­‐1)   //-­‐-­‐ { //Imposto  il  parametro  "Accept-­‐Encoding"  "deflate"  per   byteAOSB.write(data,  0,  nRead); ricevere  i  daX  in  formato  compresso   } connecXon.addRequestProperty("Accept-­‐Encoding",  "deflate"); connecXon.setRequestProperty("Content-­‐Type","applicaXon/ //-­‐-­‐         json"); //ScompaOo  i  daX  dal  server received_result  =  new  String(Library.decompressData //Invio  i  daX (received_result.getBytes())); connecXon.getOutputStream().write(compressedData); //-­‐-­‐         57
  • 58. Tiyla & BlackBerry • Java • Eclipse Sdk 58
  • 59. Tiyla & Nokia QT 59
  • 61. Windows & WP7: Supporto Nativo • Sistema di localizzazione integrato basato su file di risorse (resx), con nomi organizzati gerarchicamente a partire dal file della lingua di default. Ad esempio myRes.resx contiene le informazioni in lingua di default, mentre una eventuale traduzione in francese standard si ottiene aggiungendo il file myRes.fr.resx al progetto • Un file di risorse è composto da una serie di coppie chiave-valore. Tutti i file dovrebbero avere le stesse chiavi a cui corrispondono le versioni in lingua degli stessi testi • Le interfacce utente invocano le stringhe contenute nei file di risorse tramite la loro chiave, usando l’operatore binding • Se si vuole modificare o aggiungere una nuova lingua bisogna ricompilare il programma producendo il nuovo xap e pubblicare l’aggiornamento sul market 61
  • 62. Tiyla & WP7: Presentazione 62
  • 63. Windows & WP7: Supporto Nativo • Le chiamate al server in WP7 sono gestite in modo asincrono. • La libreria mette a disposizione una serie di eventi che vengono generati quando la chiamata è stata completata. 63
  • 64. Tiyla & WP7: Metodi (1/3)                public  delegate  void  OperationCompletedDelegate  (String  result,  Exception  error);                public  event  OperationCompletedDelegate  OperationCompleted;                ///  <summary>                ///  Profile  management                ///  create  new  profile,  or  if  exist  and  password  match  return  TRUE                ///  </summary>                              public  void  registerProfile(String  email,  String  password);                public  OperationCompletedDelegate  registerProfile_Completed;                ///  <summary>                ///  verify  your  password                ///  </summary>                public  void  loginProfile(String  email,  String  password);                public  OperationCompletedDelegate  loginProfile_Completed;                ///  <summary>                ///  remove  profile                ///  </summary>                public  void  dropProfile(String  email,  String  password);                public  OperationCompletedDelegate  dropProfile_Completed;                ///  <summary>                ///  return  data  for  profile,  if  password  is  empty  you  will  receive    informations                ///  </summary>                public  void  getProfileString(String  email,  String  password);                public  OperationCompletedDelegate  getProfileString_Completed;                ///  <summary>                ///  create  new  Application,  if  application  exists  does  do  nothing                ///  </summary>                public  void  registerApp(String  bundleId,  String  email,  String  password);                public  OperationCompletedDelegate  registerApp_Completed; 64                
  • 65. Tiyla & WP7: Metodi (2/3)                ///  <summary>                ///  set  KeyPairs  App  info  to  db                ///  </summary>                public  void  setApp(String  bundleId,  String  email,  String  password,  Dictionary<string,  string>  data);                public  OperationCompletedDelegate  setApp_Completed;                ///  <summary>                ///  Crew  manage                ///  </summary>                public  void  linkCrew(String  emailCrew,  String  bundleId,  String  email,  String  password);                public  OperationCompletedDelegate  linkCrew_Completed;                                ///  <summary>                ///  Crew  manage                ///  </summary>                                public  void  unlinkCrew(String  emailCrew,  String  bundleId,  String  email,  String  password);                public  OperationCompletedDelegate  unlinkCrew_Completed;                ///  <summary>                ///  Translations  Update  Crew                ///  </summary>                              public  void  setTApp(String  bundleId,  String  email,  String  password,  String  language,  Dictionary<string,  string>  data);                public  OperationCompletedDelegate  setTApp_Completed;                ///  <summary>                ///  Translations  Update  Developer                ///  </summary>                              public  bool  setTRankApp(String  bundleId,  String  email,  String  password,  String  language,  Dictionary<string,  string>  data);                public  OperationCompletedDelegate  setTRankApp_Completed;                ///  <summary>                ///  Translations  Client                ///  </summary>                              public  void  getApp(String  bundleId,  String  email,  String  password,  Dictionary<string,  string>  data);                public  OperationCompletedDelegate  getApp_Completed; 65
  • 66. Tiyla & WP7: Metodi (3/3) ///  <summary> ///  get  Translation  *  work  with  shots  * ///  </summary>               public  void  getTApp(String  bundleId,  String  email,  String  password,  String  language,  Dictionary<string,  string>  data); public  OperationCompletedDelegate  getTApp_Completed;                ///  <summary>                ///  get  Translation  *  work  with  shots  *                ///  </summary>                              public  void  getTApp(String  bundleId,  String  email,  String  password,  String  language,  Dictionary<string,  string>  data);                public  OperationCompletedDelegate  getTApp_Completed; 66
  • 67. Tiyla & WP7: RAPI (1/3) • Per implementare alcune funzionalità sono state usate librerie open source pubblicate da CODEPLEX: • JSON.NET - http://json.codeplex.com/releases/view/64935 • Silverlight SharpZipLib - http://slsharpziplib.codeplex.com/releases/view/50561 67
  • 68. Tiyla & WP7: RAPI (2/3)                private  void  registerProfile(String  email,  String  password,  string  method  =  "GET")                {                                                var  sender  =  new  TyilaUtils();                        sender.MyDownLoadCompletedEvent  +=  onDownloadCompleted;                        switch  (method)                        {                                case  "POST":                                        string  postData  =  JsonConvert.SerializeObject(new  command3pars()  {  func  =  "registerProfile",  email  =  email,         password  =  password  });                                        sender.executeCommandWithPost("http://tiyla.xiaprojects.com/core/echo.php",  postData);                                        break;                                case  "GET":                                default:                                        var  theUrlAndGetData  =  String.Format("func={0}&email={1}&password={2}",  "registerProfile",           HttpUtility.UrlEncode(email),  HttpUtility.UrlEncode(password));                                        theUrlAndGetData  =  "http://tiyla.xiaprojects.com/core/echo.php?"  +  theUrlAndGetData;                                        sender.executeCommandWithGet(theUrlAndGetData);                                        break;                        }                }                            private  void  onDownloadCompleted(TyilaUtils  sender,  String  content,  Exception  ex)                {                        sender.MyDownLoadCompletedEvent  -­‐=  onDownloadCompleted;                        if  (ex  !=  null)                        {                                MessageBox.Show(ex.Message);                        }                        else                        {                                MessageBox.Show(content);                        }                } 68
  • 69. Tiyla & WP7: RAPI (3/3)                public  void  executeCommandWithGet(String  theUrl)                {                        var  client  =  new  WebClient();                        client.DownloadStringCompleted  +=  new                         DownloadStringCompletedEventHandler(client_DownloadStringCompleted);                        client.DownloadStringAsync(new  Uri(theUrl));                }                private  void  client_DownloadStringCompleted(object  sender,           DownloadStringCompletedEventArgs  e)                {                        if  (MyDownLoadCompletedEvent  !=  null)                                MyDownLoadCompletedEvent(this,  e.Result,  e.Error);                } 69
  • 70. Contact us xiaprojects.com  &  @xiateam Xyla.com  &  @Xylatweets 70